package com.giraffe.device.strategy;

import com.alibaba.fastjson.JSONObject;
import com.giraffe.device.api.DeviceService;
import com.giraffe.device.pojo.dto.DeviceDTO;
import com.giraffe.device.pojo.enums.DeviceTypeEnum;
import com.google.common.collect.Lists;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;
import org.springframework.util.ObjectUtils;

import javax.annotation.Resource;
import java.util.List;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * @Author ldx
 * @Date 2024/02/21 18:30
 **/
@Slf4j
@Component
public class DeviceMessageParsingForTasmotaStrategy implements DeviceMessageParsingStrategy {

    /**
     * 二级设备消息解析策略
     */
    @Resource
    private List<SecondaryDeviceMessageParsingStrategy> secondaryDeviceMessageParsingStrategyList;

    @Resource
    private DeviceService deviceService;
    
    private static final String TELE_STATE = "tele/(.*/)*STATE"; //设备发送的状态消息，包含设备的各种信息，例如功率状态、电流、电压等。
    private static final String CMND_POWER = "cmnd/(.*/)*POWER"; //用于开关设备电源。
    private static final String STAT_RESULT = "stat/(.*/)*RESULT"; //命令执行结果反馈。
    private static final String TELE_SENSOR = "tele/(.*/)*SENSOR"; //设备上的各种传感器数据，如温湿度、光照强度等。
    private static final String CMND_BACKLOG = "cmnd/(.*/)*Backlog"; //发送指令到设备的后台任务队列。
    private static final String CMND_SET = "cmnd/(.*/)*SET"; //用于设置设备的各种参数。
    private static final String CMND_UPDATE = "cmnd/(.*/)*UPDATE"; //用于触发固件在线升级。
    private static final String TELE_INFO = "tele/(.*/)*INFO"; //提供关于设备的基本信息和统计。
    private static final String TELE_ENERGY = "tele/(.*/)*ENERGY"; //能源使用统计。

    @Override
    public String deviceTypeCode() {
        return DeviceTypeEnum.TASMOTA.getCode();
    }

    @Override
    public void parsing(String deviceId, String topic, String message) {
        log.info("deviceId:{},topic:{},message:{}", deviceId,topic, message);

        Pattern pattern = Pattern.compile(TELE_SENSOR.replace("**", "(.*/)*"));
        Matcher matcher = pattern.matcher(topic);
        if(matcher.matches()){
            parsingSecondaryDevice(message);
            return;
        }



        /*String device = deviceId.split("_")[1];
        String tempTopic = topic.replace(device, "${deviceId}");
        switch (tempTopic) {
            case TELE_STATE:
                //设备发送的状态消息，包含设备的各种信息，例如功率状态、电流、电压等。
                //{"Time":"2024-02-21T11:06:02","Uptime":"0T12:15:10","UptimeSec":44110,"Heap":139,"SleepMode":"Dynamic","Sleep":50,"LoadAvg":19,"MqttCount":2,"Berry":{"HeapUsed":3,"Objects":38}}
                break;
            case CMND_POWER:
                //用于开关设备电源。
                break;
            case STAT_RESULT:
                //命令执行结果反馈。
                break;
            case TELE_SENSOR:
                //设备上的各种传感器数据，如温湿度、光照强度等。
                //{"ZbReceived":{"0x320B":{"Device":"0x320B","Temperature":18.78,"Endpoint":1,"LinkQuality":160}}}
                //{"ZbInfo":{"0x320B":{"Device":"0x320B","IEEEAddr":"0x086BD7FFFEC9B766","ModelId":"RH3052","Manufacturer":"TUYATEC-Bfq2i2Sy","Endpoints":[1],"Config":["T01"],"Temperature":18.3,"Humidity":34.06,"Reachable":true,"BatteryPercentage":88,"BatteryLastSeenEpoch":1708509474,"LastSeen":1175,"LastSeenEpoch":1708523089,"LinkQuality":162}}}
                parsingSecondaryDevice(message);
                break;
            case CMND_BACKLOG:
        }*/
    }

    private void parsingSecondaryDevice(String message) {
        // 消息模型 ZbReceived,Zbinfo
        JSONObject baseObj = JSONObject.parseObject(message);
        JSONObject obj = new JSONObject();
        if(baseObj.containsKey("ZbReceived")){
            obj = baseObj.getJSONObject("ZbReceived");
        }else if(baseObj.containsKey("ZbInfo")){
            obj = baseObj.getJSONObject("ZbInfo");
        }
        System.out.println(obj.entrySet());
        for (Map.Entry<String,Object> m : obj.entrySet()){
            System.out.println(m.getKey());
            System.out.println(m.getValue());
            DeviceDTO dto = deviceService.getDevice(m.getKey());
            if(!ObjectUtils.isEmpty(dto)){
                SecondaryDeviceMessageParsingStrategy parsingStrategy = secondaryDeviceMessageParsingStrategyList.stream().filter(f -> f.deviceTypeCode().equals(dto.getDeviceType())).findFirst().get();
                parsingStrategy.parsing(m.getKey(),m.getValue().toString());
            }

        }

    }
}
